
#ifndef QR_CONST_H
#define QR_CONST_H

C_BEGIN_DECLS

#define QR_VERSION_MIN 1
#define QR_VERSION_MAX 40
#define QR_WIDTH_MIN 21
#define QR_WIDTH_MAX 177

#define MODE_INDICATOR_LENGTH 4
#define MODE_NUM_INDICATOR 0x1
#define MODE_ALPHANUM_INDICATOR 0x2
#define MODE_8BIT_INDICATOR 0x4
#define MODE_KANJI_INDICATOR 0x8

#define PNG_MARGIN 4
#define PNG_SIZE 3

typedef enum
{
	QR_MODE_INVALID = -1,
	QR_MODE_NUM,
	QR_MODE_ALPHANUM,
	QR_MODE_8BIT,
	QR_MODE_KANJI,
	QR_MODE_COUNT
} QRMode;

typedef enum
{
	EC_LEVEL_INVALID = -1,
	EC_LEVEL_L,
	EC_LEVEL_M,
	EC_LEVEL_Q,
	EC_LEVEL_H,
	EC_LEVEL_COUNT
} ECLevel;

typedef enum
{
	MASK_PATTERN_INVALID = -1,
	MASK_PATTERN0,
	MASK_PATTERN1,
	MASK_PATTERN2,
	MASK_PATTERN3,
	MASK_PATTERN4,
	MASK_PATTERN5,
	MASK_PATTERN6,
	MASK_PATTERN7,
	MASK_PATTERN_COUNT
} MaskPattern;

typedef enum
{
	FILL_STATE_INVALID = -1,
	FILL_STATE_LEFT_BLANK,
	FILL_STATE_LEFT_FULL
} FillState;

typedef enum
{
	FILL_DIRECTION_UPPER = -1,
	FILL_DIRECTION_LOWER = 1
} FillDirection;


static const int characterCountIndicatorLengthTable[3][QR_MODE_COUNT] =
{
	{10, 9, 9, 8},
	{12, 11, 16, 10},
	{14, 13, 16, 12}
};

typedef struct
{
	int _words;
	int _remainder;	// bits
	int _ec_words[EC_LEVEL_COUNT];
} QRCapacity;

static const QRCapacity qrCapacity[QR_VERSION_MAX + 1] =
{
	{0,	0,	{0,	0,	0,	0}},	// version 0(invalid)
	{26,	0,	{7,	10,	13,	17}},
	{44,	7,	{10,	16,	22,	28}},
	{70,	7,	{15,	26,	36,	44}},
	{100,	7,	{20,	36,	52,	64}},
	{134,	7,	{26,	48,	72,	88}},	// 5
	{172,	7,	{36,	64,	96,	112}},
	{196,	0,	{40,	72,	108,	130}},
	{242,	0,	{48,	88,	132,	156}},
	{292,	0,	{60,	110,	160,	192}},
	{346,	0,	{72,	130,	192,	224}},	// 10
	{404,	0,	{80,	150,	224,	264}},
	{466,	0,	{96,	176,	260,	308}},
	{532,	0,	{104,	198,	288,	352}},
	{581,	3,	{120,	216,	320,	384}},
	{655,	3,	{132,	240,	360,	432}},	// 15
	{733,	3,	{144,	280,	408,	480}},
	{815,	3,	{168,	308,	448,	532}},
	{901,	3,	{180,	338,	504,	588}},
	{991,	3,	{196,	364,	546,	650}},
	{1085,	3,	{224,	416,	600,	700}},	// 20
	{1156,	4,	{224,	442,	644,	750}},
	{1258,	4,	{252,	476,	690,	816}},
	{1364,	4,	{270,	504,	750,	900}},
	{1474,	4,	{300,	560,	810,	960}},
	{1588,	4,	{312,	588,	870,	1050}},	// 25
	{1706,	4,	{336,	644,	952,	1110}},
	{1828,	4,	{360,	700,	1020,	1200}},
	{1921,	3,	{390,	728,	1050,	1260}},
	{2051,	3,	{420,	784,	1140,	1350}},
	{2185,	3,	{450,	812,	1200,	1440}},	// 30
	{2323,	3,	{480,	868,	1290,	1530}},
	{2465,	3,	{510,	924,	1350,	1620}},
	{2611,	3,	{540,	980,	1440,	1710}},
	{2761,	3,	{570,	1036,	1530,	1800}},
	{2876,	0,	{570,	1064,	1590,	1890}},	// 35
	{3034,	0,	{600,	1120,	1680,	1980}},
	{3196,	0,	{630,	1204,	1770,	2100}},
	{3362,	0,	{660,	1260,	1860,	2220}},
	{3532,	0,	{720,	1316,	1950,	2310}},
	{3706,	0,	{750,	1372,	2040,	2430}}	// 40
};

static const int eccTable[QR_VERSION_MAX + 1][EC_LEVEL_COUNT][2] =
{
	{{0,    0}, {0,    0}, {0,    0}, {0,    0}},	// version 0(invalid)
	{{1,    0}, {1,    0}, {1,    0}, {1,    0}},
	{{1,    0}, {1,    0}, {1,    0}, {1,    0}},
	{{1,    0}, {1,    0}, {2,    0}, {2,    0}},
	{{1,    0}, {2,    0}, {2,    0}, {4,    0}},
	{{1,    0}, {2,    0}, {2,    2}, {2,    2}},	// 5
	{{2,    0}, {4,    0}, {4,    0}, {4,    0}},
	{{2,    0}, {4,    0}, {2,    4}, {4,    1}},
	{{2,    0}, {2,    2}, {4,    2}, {4,    2}},
	{{2,    0}, {3,    2}, {4,    4}, {4,    4}},
	{{2,    2}, {4,    1}, {6,    2}, {6,    2}},	// 10
	{{4,    0}, {1,    4}, {4,    4}, {3,    8}},
	{{2,    2}, {6,    2}, {4,    6}, {7,    4}},
	{{4,    0}, {8,    1}, {8,    4}, {12,   4}},
	{{3,    1}, {4,    5}, {11,   5}, {11,   5}},
	{{5,    1}, {5,    5}, {5,    7}, {11,   7}},	// 15
	{{5,    1}, {7,    3}, {15,   2}, {3,   13}},
	{{1,    5}, {10,   1}, {1,   15}, {2,   17}},
	{{5,    1}, {9,    4}, {17,   1}, {2,   19}},
	{{3,    4}, {3,   11}, {17,   4}, {9,   16}},
	{{3,    5}, {3,   13}, {15,   5}, {15,  10}},	// 20
	{{4,    4}, {17,   0}, {17,   6}, {19,   6}},
	{{2,    7}, {17,   0}, {7,   16}, {34,   0}},
	{{4,    5}, {4,   14}, {11,  14}, {16,  14}},
	{{6,    4}, {6,   14}, {11,  16}, {30,   2}},
	{{8,    4}, {8,   13}, {7,   22}, {22,  13}},	// 25
	{{10,   2}, {19,   4}, {28,   6}, {33,   4}},
	{{8,    4}, {22,   3}, {8,   26}, {12,  28}},
	{{3,   10}, {3,   23}, {4,   31}, {11,  31}},
	{{7,    7}, {21,   7}, {1,   37}, {19,  26}},
	{{5,   10}, {19,  10}, {15,  25}, {23,  25}},	// 30
	{{13,   3}, {2,   29}, {42,   1}, {23,  28}},
	{{17,   0}, {10,  23}, {10,  35}, {19,  35}},
	{{17,   1}, {14,  21}, {29,  19}, {11,  46}},
	{{13,   6}, {14,  23}, {44,   7}, {59,   1}},
	{{12,   7}, {12,  26}, {39,  14}, {22,  41}},	// 35
	{{6,   14}, {6,   34}, {46,  10}, {2,   64}},
	{{17,   4}, {29,  14}, {49,  10}, {24,  46}},
	{{4,   18}, {13,  32}, {48,  14}, {42,  32}},
	{{20,   4}, {40,   7}, {43,  22}, {10,  67}},
	{{19,   6}, {18,  31}, {34,  34}, {20,  61}}	// 40
};

static const unsigned char finderPattern[49] =
{
	0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1,
	0xc1, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc1,
	0xc1, 0xc0, 0xc1, 0xc1, 0xc1, 0xc0, 0xc1,
	0xc1, 0xc0, 0xc1, 0xc1, 0xc1, 0xc0, 0xc1,
	0xc1, 0xc0, 0xc1, 0xc1, 0xc1, 0xc0, 0xc1,
	0xc1, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc1,
	0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1
};

static const unsigned char alignmentPattern[25] =
{
	0xa1, 0xa1, 0xa1, 0xa1, 0xa1,
	0xa1, 0xa0, 0xa0, 0xa0, 0xa1,
	0xa1, 0xa0, 0xa1, 0xa0, 0xa1,
	0xa1, 0xa0, 0xa0, 0xa0, 0xa1,
	0xa1, 0xa1, 0xa1, 0xa1, 0xa1
};

static const int alignmentPatternPosition[QR_VERSION_MAX + 1][2] =
{
	{0,   0},						// version 0(invalid)
	{0,   0}, {18,  0}, {22,  0}, {26,  0}, {30,  0},	// 1  - 5
	{34,  0}, {22, 38}, {24, 42}, {26, 46}, {28, 50},	// 6  - 10
	{30, 54}, {32, 58}, {34, 62}, {26, 46}, {26, 48},	// 11 - 15
	{26, 50}, {30, 54}, {30, 56}, {30, 58}, {34, 62},	// 16 - 20
	{28, 50}, {26, 50}, {30, 54}, {28, 54}, {32, 58},	// 21 - 25
	{30, 58}, {34, 62}, {26, 50}, {30, 54}, {26, 52},	// 26 - 30
	{30, 56}, {34, 60}, {30, 58}, {34, 62}, {30, 54},	// 31 - 35
	{24, 50}, {28, 54}, {32, 58}, {26, 54}, {30, 58}	// 35 - 40
};

static const unsigned int versionInformationPattern[QR_VERSION_MAX + 1] =
{
	0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,			// version 0 - 6(invalid)
	         0x07c94, 0x085bc, 0x09a99, 0x0a4d3,		// 7  - 10
	0x0bbf6, 0x0c762, 0x0d847, 0x0e60d, 0x0f928,		// 11 - 15
	0x10b78, 0x1145d, 0x12a17, 0x13532, 0x149a6,		// 16 - 20
	0x15683, 0x168c9, 0x177ec, 0x18ec4, 0x191e1,		// 21 - 25
	0x1afab, 0x1b08e, 0x1cc1a, 0x1d33f, 0x1ed75,		// 26 - 30
	0x1f250, 0x209d5, 0x216f0, 0x228ba, 0x2379f,		// 31 - 35
	0x24b0b, 0x2542e, 0x26a64, 0x27541, 0x28c69		// 36 - 40
};

static const unsigned int formatInformation[EC_LEVEL_COUNT][MASK_PATTERN_COUNT] =
{
	{0x77c4, 0x72f3, 0x7daa, 0x789d, 0x662f, 0x6318, 0x6c41, 0x6976},
	{0x5412, 0x5125, 0x5e7c, 0x5b4b, 0x45f9, 0x40ce, 0x4f97, 0x4aa0},
	{0x355f, 0x3068, 0x3f31, 0x3a06, 0x24b4, 0x2183, 0x2eda, 0x2bed},
	{0x1689, 0x13be, 0x1ce7, 0x19d0, 0x0762, 0x0255, 0x0d0c, 0x083b}
};

C_END_DECLS

#endif	// QR_CONST_H

